"""
交易分析器模块

提供交易记录分析、性能统计和报告生成功能
"""

from typing import Dict, List, Any, Optional
from datetime import datetime, timedelta
from dataclasses import dataclass
import statistics


@dataclass
class TradeRecord:
    """交易记录"""
    symbol: str
    side: str  # 'buy' or 'sell'
    amount: float
    price: float
    timestamp: datetime
    commission: float = 0.0
    order_id: str = ""


class TradeAnalyzer:
    """交易分析器"""
    
    def __init__(self):
        self.trades: List[TradeRecord] = []
        self.positions: Dict[str, float] = {}  # symbol -> amount
        self.realized_pnl = 0.0
        
    def add_trade(self, symbol: str, side: str, amount: float, price: float, 
                  timestamp: datetime, commission: float = 0.0, order_id: str = ""):
        """添加交易记录"""
        trade = TradeRecord(
            symbol=symbol,
            side=side,
            amount=amount,
            price=price,
            timestamp=timestamp,
            commission=commission,
            order_id=order_id
        )
        
        self.trades.append(trade)
        
        # 更新持仓
        if symbol not in self.positions:
            self.positions[symbol] = 0.0
            
        if side == 'buy':
            self.positions[symbol] += amount
        else:  # sell
            self.positions[symbol] -= amount
            
        # 计算已实现盈亏（简化版本）
        if side == 'sell':
            # 找到对应的买入记录计算盈亏
            buy_trades = [t for t in self.trades if t.symbol == symbol and t.side == 'buy']
            if buy_trades:
                avg_buy_price = sum(t.price * t.amount for t in buy_trades) / sum(t.amount for t in buy_trades)
                pnl = (price - avg_buy_price) * amount - commission
                self.realized_pnl += pnl
    
    def get_trade_count(self) -> int:
        """获取交易总数"""
        return len(self.trades)
    
    def get_profitable_trades(self) -> int:
        """获取盈利交易数（简化计算）"""
        profitable = 0
        symbol_trades = {}
        
        # 按交易对分组
        for trade in self.trades:
            if trade.symbol not in symbol_trades:
                symbol_trades[trade.symbol] = []
            symbol_trades[trade.symbol].append(trade)
        
        # 计算每个交易对的盈利交易
        for symbol, trades in symbol_trades.items():
            buy_trades = [t for t in trades if t.side == 'buy']
            sell_trades = [t for t in trades if t.side == 'sell']
            
            if buy_trades and sell_trades:
                avg_buy = sum(t.price * t.amount for t in buy_trades) / sum(t.amount for t in buy_trades)
                avg_sell = sum(t.price * t.amount for t in sell_trades) / sum(t.amount for t in sell_trades)
                
                if avg_sell > avg_buy:
                    profitable += len(sell_trades)
        
        return profitable
    
    def get_losing_trades(self) -> int:
        """获取亏损交易数"""
        return len([t for t in self.trades if t.side == 'sell']) - self.get_profitable_trades()
    
    def get_win_rate(self) -> float:
        """获取胜率"""
        sell_trades = len([t for t in self.trades if t.side == 'sell'])
        if sell_trades == 0:
            return 0.0
        return self.get_profitable_trades() / sell_trades
    
    def get_total_pnl(self) -> float:
        """获取总盈亏"""
        return self.realized_pnl
    
    def get_average_pnl(self) -> float:
        """获取平均盈亏"""
        sell_trades = len([t for t in self.trades if t.side == 'sell'])
        if sell_trades == 0:
            return 0.0
        return self.realized_pnl / sell_trades
    
    def get_max_profit(self) -> float:
        """获取最大盈利（简化计算）"""
        profits = []
        symbol_trades = {}
        
        # 按交易对分组
        for trade in self.trades:
            if trade.symbol not in symbol_trades:
                symbol_trades[trade.symbol] = []
            symbol_trades[trade.symbol].append(trade)
        
        # 计算每个交易对的盈利
        for symbol, trades in symbol_trades.items():
            buy_trades = [t for t in trades if t.side == 'buy']
            sell_trades = [t for t in trades if t.side == 'sell']
            
            for sell_trade in sell_trades:
                for buy_trade in buy_trades:
                    if buy_trade.timestamp < sell_trade.timestamp:
                        profit = (sell_trade.price - buy_trade.price) * min(sell_trade.amount, buy_trade.amount)
                        profits.append(profit)
        
        return max(profits) if profits else 0.0
    
    def get_max_loss(self) -> float:
        """获取最大亏损（简化计算）"""
        losses = []
        symbol_trades = {}
        
        # 按交易对分组
        for trade in self.trades:
            if trade.symbol not in symbol_trades:
                symbol_trades[trade.symbol] = []
            symbol_trades[trade.symbol].append(trade)
        
        # 计算每个交易对的亏损
        for symbol, trades in symbol_trades.items():
            buy_trades = [t for t in trades if t.side == 'buy']
            sell_trades = [t for t in trades if t.side == 'sell']
            
            for sell_trade in sell_trades:
                for buy_trade in buy_trades:
                    if buy_trade.timestamp < sell_trade.timestamp:
                        loss = (sell_trade.price - buy_trade.price) * min(sell_trade.amount, buy_trade.amount)
                        if loss < 0:
                            losses.append(abs(loss))
        
        return max(losses) if losses else 0.0
    
    def get_trading_volume(self) -> float:
        """获取交易量"""
        return sum(trade.amount * trade.price for trade in self.trades)
    
    def get_commission_paid(self) -> float:
        """获取支付的手续费"""
        return sum(trade.commission for trade in self.trades)
    
    def get_trades_by_symbol(self, symbol: str) -> List[TradeRecord]:
        """获取指定交易对的交易记录"""
        return [trade for trade in self.trades if trade.symbol == symbol]
    
    def get_trades_by_date_range(self, start_date: datetime, end_date: datetime) -> List[TradeRecord]:
        """获取指定日期范围的交易记录"""
        return [trade for trade in self.trades 
                if start_date <= trade.timestamp <= end_date]
    
    def generate_report(self) -> Dict[str, Any]:
        """生成交易报告"""
        total_trades = self.get_trade_count()
        profitable_trades = self.get_profitable_trades()
        losing_trades = self.get_losing_trades()
        
        return {
            'total_trades': total_trades,
            'profitable_trades': profitable_trades,
            'losing_trades': losing_trades,
            'win_rate': self.get_win_rate(),
            'total_pnl': self.get_total_pnl(),
            'avg_pnl': self.get_average_pnl(),
            'max_profit': self.get_max_profit(),
            'max_loss': self.get_max_loss(),
            'trading_volume': self.get_trading_volume(),
            'commission_paid': self.get_commission_paid(),
            'current_positions': self.positions.copy(),
            'report_time': datetime.now().strftime('%Y-%m-%d %H:%M:%S')
        }
    
    def get_daily_pnl(self) -> Dict[str, float]:
        """获取每日盈亏"""
        daily_pnl = {}
        
        for trade in self.trades:
            date_str = trade.timestamp.strftime('%Y-%m-%d')
            if date_str not in daily_pnl:
                daily_pnl[date_str] = 0.0
            
            # 简化的盈亏计算
            if trade.side == 'sell':
                # 假设卖出时计算盈亏
                daily_pnl[date_str] += trade.amount * trade.price * 0.001  # 假设0.1%的收益率
        
        return daily_pnl
    
    def get_monthly_summary(self) -> Dict[str, Dict[str, Any]]:
        """获取月度汇总"""
        monthly_data = {}
        
        for trade in self.trades:
            month_key = trade.timestamp.strftime('%Y-%m')
            if month_key not in monthly_data:
                monthly_data[month_key] = {
                    'trades': 0,
                    'volume': 0.0,
                    'commission': 0.0
                }
            
            monthly_data[month_key]['trades'] += 1
            monthly_data[month_key]['volume'] += trade.amount * trade.price
            monthly_data[month_key]['commission'] += trade.commission
        
        return monthly_data
    
    def clear_trades(self):
        """清空交易记录"""
        self.trades.clear()
        self.positions.clear()
        self.realized_pnl = 0.0


# 创建全局实例
trade_analyzer = TradeAnalyzer()